macro_rules! create_func {
    ($func_name: ident) => {
        fn $func_name() {
            println!("create--func: {:?}", stringify!($func_name));
        }
    };
}
create_func!(foo);
create_func!(bar);

macro_rules! print_result {
    ($experssion: expr) => {
        println!("{:?} = {:?}",
            stringify!($experssion),
            $experssion);
    };
}

macro_rules! test {
    ($left:expr; and $right:expr) => {
        println!("{:?} and {:?} is {:?}", 
            stringify!($left),
            stringify!($right),
            $left && $right);
    };
    ($left:expr; or $right:expr) => {
        println!("{:?} or {:?} is {:?}",
            stringify!($left),
            stringify!($right),
            $left || $right);
    }
}

macro_rules! find_min {
    ($x:expr) => ($x);
    ($x:expr, $($y:expr),+) => {
        std::cmp::min($x, find_min!($($y),+))
    }
}

pub fn main() {
    foo();
    bar();

    print_result!(1 + 3 + 5 + 1999);

    test!(true; and false);
    test!(true; or false);

    println!("{}", find_min!(1, 23, -1, 4, 5));
}
